package com.itfreer.gis.data.server;

import java.util.ArrayList;
import java.util.List;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.util.EntityUtils;
import org.geotools.data.crs.ForceCoordinateSystemFeatureResults;
import org.geotools.data.simple.SimpleFeatureIterator;
import org.geotools.feature.FeatureCollection;
import org.geotools.feature.simple.SimpleFeatureBuilder;
import org.geotools.feature.simple.SimpleFeatureTypeBuilder;
import org.geotools.geojson.feature.FeatureJSON;
import org.geotools.geojson.geom.GeometryJSON;
import org.geotools.referencing.CRS;
import org.locationtech.jts.geom.Geometry;
import org.opengis.feature.simple.SimpleFeature;
import org.opengis.feature.simple.SimpleFeatureType;
import org.opengis.feature.type.AttributeDescriptor;

public class GisHttpUtil {

	public static List<SimpleFeature> post(String url, List<NameValuePair> params) {

		// 创建HTTP客户端
		CloseableHttpClient httpclient = HttpClientBuilder.create().setDefaultRequestConfig(GisConstants.REQUEST_CONFIG)
				.build();
		// 创建POST请求
		HttpPost httpPost = new HttpPost(url.toString());
		
		try {
			// 设置请求体为xml
			HttpEntity entity = new UrlEncodedFormEntity(params, GisConstants.DEFAULT_CHARSET);
			httpPost.setEntity(entity);
			// 发送请求
			HttpResponse response= httpclient.execute(httpPost);
			if (response.getStatusLine().getStatusCode() == 200) {
				return jsonToFeatures(response);
			}
		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			try {
				httpclient.close();
			} catch (final Exception e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		return null; 
	}

	@SuppressWarnings("unchecked")
	public static List<SimpleFeature> jsonToFeatures(HttpResponse response) {
		// 调用EntityUtils.toString方法最后会自动把inputStream close掉的
		try {
			String geoJsonStr = EntityUtils.toString(response.getEntity());
			// 指定GeometryJSON构造器，15位小数
			FeatureJSON fjson_15 = new FeatureJSON(new GeometryJSON(15));// fjson_15已经保留15位
			// 解决默认无坐标系
			fjson_15.setEncodeFeatureCollectionCRS(true);
			fjson_15.setEncodeFeatureCRS(true);
			// 添加空值输出
			fjson_15.setEncodeNullValues(true);

			// 读取为FeatureCollection
			FeatureCollection<SimpleFeatureType, SimpleFeature> featureCollection = fjson_15
					.readFeatureCollection(geoJsonStr);
			// 获取SimpleFeatureType
			SimpleFeatureType simpleFeatureType = (SimpleFeatureType) featureCollection.getSchema();

			// 解决坐标系错误问题
			String srs = CRS.lookupIdentifier(simpleFeatureType.getCoordinateReferenceSystem(), true); // 获取EPSG
			featureCollection = new ForceCoordinateSystemFeatureResults(featureCollection, CRS.decode(srs, true));

			SimpleFeatureType simpleFeatureType2 = (SimpleFeatureType) featureCollection.getSchema();

			SimpleFeatureType newType = retype(simpleFeatureType2);

			List<SimpleFeature> simpleFeatureList = new ArrayList<SimpleFeature>();
			SimpleFeatureIterator iterator = (SimpleFeatureIterator) featureCollection.features();
			while (iterator.hasNext()) {
				SimpleFeature newFeature = retypeFeature(iterator.next(), newType);
				simpleFeatureList.add(newFeature);
			}
			iterator.close();
			return simpleFeatureList;
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
			return null;
		}
	}

	/**
	 * 构建新的SimpleFeatureType
	 * 
	 * @param filterGeometry
	 * @param geometryField
	 * @return
	 */
	private static SimpleFeatureType retype(SimpleFeatureType oldType) {
		SimpleFeatureTypeBuilder typeBuilder = new SimpleFeatureTypeBuilder();
		typeBuilder.init(oldType);
		// the_geom
		if ("geometry".equals(oldType.getGeometryDescriptor().getLocalName())) {
			typeBuilder.remove("geometry");
			typeBuilder.add("the_geom", oldType.getType("geometry").getBinding());
		}
		// 生成新的SimpleFeatureType
		return typeBuilder.buildFeatureType();
	}

	// 新建一个方法，用于变换feature的type
	private static SimpleFeature retypeFeature(SimpleFeature feature, SimpleFeatureType newType) {
		SimpleFeatureBuilder builder = new SimpleFeatureBuilder(newType);
		// 遍历属性
		for (AttributeDescriptor att : newType.getAttributeDescriptors()) {
			Object value = feature.getAttribute(att.getName());
			// 空间列
			if (Geometry.class.isAssignableFrom(att.getType().getBinding())) {
				builder.set("the_geom", feature.getDefaultGeometry());
				continue;
			}
			builder.set(att.getName(), value);
		}
		return builder.buildFeature(feature.getID());
	}
}
